package lhy.orm;

import it.unimi.dsi.fastutil.objects.Object2ObjectArrayMap;
import it.unimi.dsi.fastutil.objects.ReferenceArrayList;
import lhy.AppStart;
import lhy.orm.model.EntityData;
import lhy.orm.model.FieldData;
import lhy.lhyorm.table.DatabaseTable;
import lhy.utils.PropertyUtils;
import lhy.utils.ReflectUtils;
import org.reflections.Reflections;
import org.reflections.scanners.Scanners;

import java.util.List;
import java.util.Map;
import java.util.Properties;

public class UniLoader {
    public static final UniLoader INSTANCE = new UniLoader();
    public static final Map<String,EntityData> entityNameClassMap = new Object2ObjectArrayMap<>();
   // public static final Map<String,List<?>> entityTableObjectCacheMap = new Reference2ReferenceArrayMap<>();
    private UniLoader(){}
    public void loadEntities(){
        Properties prop= PropertyUtils.loadProps("orm.properties");
        String basePackage = prop.getProperty("base_package");
        AppStart.LOGGER.info("扫描实体包 {}",basePackage);
        Reflections reflections = new Reflections(basePackage, Scanners.TypesAnnotated);
        reflections.getTypesAnnotatedWith(DatabaseTable.class).forEach(clz ->{
            String entityTableName = OrmUtils.getEntityTableName(clz);
            String classFullName = ReflectUtils.getClassFullName(clz);
            String classComment = OrmUtils.getEntityComment(clz);
            boolean basicBean = OrmUtils.isClassBasicBean(clz);
            boolean treeStructure = OrmUtils.isClassTreeStructure(clz);
            boolean viewOnly = OrmUtils.isEntityViewOnly(clz);
            AppStart.LOGGER.info("载入实体类 {} {}  ",classComment,classFullName);
            final List<FieldData> fieldDataList = new ReferenceArrayList<>();
            ReflectUtils.getAccessibleFieldsList(clz).forEach(field -> {
                String fieldName = ReflectUtils.getFieldName(field);
                String fieldComment = OrmUtils.getFieldDescription(field);
                String typeClassName = ReflectUtils.getClassFullName(field.getType());
                String typeClassShortName = ReflectUtils.getClassShortName(field.getType());
                boolean identity = OrmUtils.isFieldIdentity(field);
                boolean autoIncrement = OrmUtils.isFieldAutoIncrement(field);
                boolean nullable = OrmUtils.isFieldNullable(field);
                boolean foreignKey = OrmUtils.isFieldHasForeignKey(field);
                FieldData fieldData = new FieldData(fieldName,fieldComment,typeClassName,typeClassShortName,identity,autoIncrement,nullable,foreignKey);
                fieldDataList.add(fieldData);
            });
            EntityData entityData = new EntityData(entityTableName,classFullName,classComment,basicBean,treeStructure,viewOnly,fieldDataList.toArray(new FieldData[0]));
            entityNameClassMap.put(classFullName,entityData);
        });
        AppStart.LOGGER.info("所有实体类与字段，载入完成，共 {} 条",entityNameClassMap.size());

    }
    public void loadCache(){
        /*entityNameClassMap.entrySet().forEach(entry->{
            String clzName = entry.getKey();
            List<?> objList = new GenericDaoImpl<>(ReflectUtils.loadClassByName(clzName)).get();
            AppStart.LOGGER.info("载入缓存： {}",StringUtils.join(objList, ","));
            entityTableObjectCacheMap.put(clzName,objList);
        });
        AppStart.LOGGER.info("载入缓存： {}",StringUtils.join(entityTableObjectCacheMap, ","));*/
        /*AppStart.LOGGER.info("开始载入基础数据类缓存");
        Map<String, EntityData> basicBeanMap = entityNameClassMap.entrySet().stream()
                .filter(entry->entry.getValue().isBasicBean())
                .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
        Map<String, EntityData> advancedBeanMap = entityNameClassMap.entrySet().stream()
                .filter(entry->!entry.getValue().isBasicBean())
                .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));


        basicBeanMap.forEach((classFullName,ENTITY_DATA)->{
            String entityFullName = ENTITY_DATA.getEntityFullName();
            Class<?> entityClass = ReflectUtils.loadClassByName(entityFullName);
            String tableName = OrmUtils.getEntityTableName(entityClass);
            AppStart.LOGGER.info("载入缓存 {} {}，表名：{}",ENTITY_DATA.getEntityComment(), entityFullName,tableName);
            List<?> objectsList = new GenericDaoImpl<>(entityClass).getAll();
            entityTableObjectMap.put(entityFullName,objectsList);
        });
        AppStart.LOGGER.info("基础数据类缓存，载入完成，共 {} 条",entityTableObjectMap.size());

        advancedBeanMap.forEach((classFullName,ENTITY_DATA)->{


        });*/

    }
}
